/**
 * 配置管理器
 * 管理固件、车型、电机配置
 * 服务器地址: https://bin.dunen.com.cn/release/
 */
const IniParser = require('./iniParser.js');

class ConfigManager {
  constructor() {
    this.baseUrl = 'https://bin.dunen.com.cn/release/';
    this.configFile = 'typeBin64.inf';
    this.configData = null; // 缓存配置数据
    this.cacheKey = 'dunen_config_cache';
    this.cacheExpireTime = 24 * 60 * 60 * 1000; // 24小时缓存
  }

  /**
   * 加载配置文件
   * @param {boolean} forceRefresh - 是否强制刷新
   */
  async loadConfig(forceRefresh = false) {
    // 1. 检查内存缓存
    if (!forceRefresh && this.configData) {
      console.log('[Config] 使用内存缓存');
      return this.configData;
    }

    // 2. 检查本地存储
    if (!forceRefresh) {
      const cached = this.getCache();
      if (cached) {
        this.configData = cached;
        return this.configData;
      }
    }

    // 3. 从服务器下载
    try {
      console.log('[Config] 下载配置文件:', this.baseUrl + this.configFile);
      
      const content = await this.downloadConfig();
      this.configData = IniParser.parse(content);
      
      // 保存到本地缓存
      this.setCache(this.configData);
      
      const count = Object.keys(this.configData).length;
      console.log('[Config] 配置加载成功，共', count, '个型号');
      
      return this.configData;

    } catch (error) {
      console.error('[Config] 加载配置失败:', error);
      throw error;
    }
  }

  /**
   * 下载配置文件
   */
  downloadConfig() {
    return new Promise((resolve, reject) => {
      wx.request({
        url: this.baseUrl + this.configFile,
        method: 'GET',
        timeout: 15000,
        success: (res) => {
          if (res.statusCode === 200) {
            resolve(res.data);
          } else {
            reject(new Error(`下载失败: HTTP ${res.statusCode}`));
          }
        },
        fail: (err) => {
          reject(new Error('网络请求失败: ' + err.errMsg));
        }
      });
    });
  }

  /**
   * 获取控制器配置
   * @param {string} mcuType - 控制器型号
   */
  async getControllerConfig(mcuType) {
    if (!this.configData) {
      await this.loadConfig();
    }

    const config = IniParser.getSection(this.configData, mcuType);
    
    if (!config) {
      console.warn('[Config] 未找到型号:', mcuType);
      return null;
    }

    // 提取版本号（如果配置文件有version字段则使用，否则从binFile文件名中提取）
    let version = config.version || null;
    if (!version && config.binFile) {
      // 从文件名中提取版本号，支持多种格式：
      // 1. V1108 或 v1108 (纯数字)
      // 2. v1.2.3 或 V1.2.3 (带点号)
      // 3. _V1108.bin, -v1.2.3.bin 等
      let versionMatch = config.binFile.match(/[_\-]?[vV](\d+\.\d+(\.\d+)?)/); // 优先匹配 v1.2.3 格式
      if (!versionMatch) {
        versionMatch = config.binFile.match(/[_\-]?[vV](\d{4})/); // 匹配 V1108 格式（4位数字）
      }
      if (!versionMatch) {
        versionMatch = config.binFile.match(/[_\-]?[vV](\d+)/); // 匹配任意数字
      }
      version = versionMatch ? versionMatch[1] : null;
    }

    return {
      mcuType: mcuType,
      binFile: config.binFile || null,
      version: version, // 云端固件版本号
      xlsxFile: config.xlsxFile || null,
      motorSetFile: config.motorSetFile || null,
      vehicleSetFile: config.vehicleSetFile || null,
      // 构造完整URL
      binUrl: config.binFile ? this.baseUrl + config.binFile : null,
      xlsxUrl: config.xlsxFile ? this.baseUrl + config.xlsxFile : null,
      motorUrl: (config.motorSetFile && config.motorSetFile !== 'None_Motor_Set.ini') 
        ? this.baseUrl + config.motorSetFile 
        : null,
      vehicleUrl: (config.vehicleSetFile && config.vehicleSetFile !== 'None_Vehicle_Set.ini') 
        ? this.baseUrl + config.vehicleSetFile 
        : null
    };
  }

  /**
   * 获取所有支持的型号列表
   */
  async getAllModels() {
    if (!this.configData) {
      await this.loadConfig();
    }

    return IniParser.getSections(this.configData);
  }

  /**
   * 搜索型号（模糊匹配）
   * @param {string} keyword - 搜索关键词
   */
  async searchModels(keyword) {
    const allModels = await this.getAllModels();
    
    if (!keyword) {
      return allModels;
    }

    const lowerKeyword = keyword.toLowerCase();
    return allModels.filter(model => 
      model.toLowerCase().includes(lowerKeyword)
    );
  }

  /**
   * 下载文件
   * @param {string} url - 文件URL
   * @param {function} onProgress - 进度回调
   */
  downloadFile(url, onProgress) {
    return new Promise((resolve, reject) => {
      console.log('[Config] 下载文件:', url);

      const downloadTask = wx.downloadFile({
        url: url,
        timeout: 60000, // 60秒超时
        success: (res) => {
          if (res.statusCode === 200) {
            console.log('[Config] 文件下载成功');
            resolve(res.tempFilePath);
          } else {
            reject(new Error(`下载失败: HTTP ${res.statusCode}`));
          }
        },
        fail: (err) => {
          reject(new Error('下载失败: ' + err.errMsg));
        }
      });

      // 监听下载进度
      if (onProgress) {
        downloadTask.onProgressUpdate(onProgress);
      }
    });
  }

  /**
   * 读取文件内容
   * @param {string} filePath - 文件路径
   * @param {string} encoding - 编码格式 ('utf8' 或 'binary')
   */
  readFile(filePath, encoding = 'utf8') {
    return new Promise((resolve, reject) => {
      const fs = wx.getFileSystemManager();
      
      fs.readFile({
        filePath: filePath,
        encoding: encoding === 'utf8' ? 'utf8' : undefined,
        success: (res) => {
          if (encoding === 'binary') {
            resolve(new Uint8Array(res.data));
          } else {
            resolve(res.data);
          }
        },
        fail: (err) => {
          reject(new Error('读取文件失败: ' + err.errMsg));
        }
      });
    });
  }

  /**
   * 获取缓存
   */
  getCache() {
    try {
      const cache = wx.getStorageSync(this.cacheKey);
      if (cache && cache.data && cache.timestamp) {
        const age = Date.now() - cache.timestamp;
        if (age < this.cacheExpireTime) {
          console.log('[Config] 使用本地缓存，已缓存', Math.floor(age / 1000 / 60), '分钟');
          return cache.data;
        } else {
          console.log('[Config] 缓存已过期');
        }
      }
    } catch (error) {
      console.error('[Config] 读取缓存失败:', error);
    }
    return null;
  }

  /**
   * 设置缓存
   */
  setCache(data) {
    try {
      wx.setStorageSync(this.cacheKey, {
        data: data,
        timestamp: Date.now()
      });
      console.log('[Config] 配置已缓存');
    } catch (error) {
      console.error('[Config] 设置缓存失败:', error);
    }
  }

  /**
   * 清除缓存
   */
  clearCache() {
    try {
      wx.removeStorageSync(this.cacheKey);
      this.configData = null;
      console.log('[Config] 缓存已清除');
    } catch (error) {
      console.error('[Config] 清除缓存失败:', error);
    }
  }
}

module.exports = ConfigManager;

